package org.galaxyworld.flycode.jobs;

import org.apache.commons.lang3.StringUtils;
import org.beetl.core.Template;
import org.galaxyworld.flycode.config.*;
import org.galaxyworld.flycode.core.TemplateManager;
import org.galaxyworld.flycode.utils.FileWriterUtils;
import org.galaxyworld.flycode.utils.NameUtils;

import java.io.Writer;
import java.util.HashMap;
import java.util.Map;

public class Service {

    private String className;

    private String serviceName;

    private String serviceImplName;

    private String serviceTestName;

    private String tableName;

    public Service() {
        AppConfigData appConfigData = ConfigManager.getConfig(AppConfigData.class);
        ServiceConfigData serviceConfigData = ConfigManager.getConfig(ServiceConfigData.class);
        ModelConfigData modelConfigData = ConfigManager.getConfig(ModelConfigData.class);

        TemplateManager templateManager = TemplateManager.getInstance();

        Map<String, Object> shared = new HashMap<>();
        shared.put("java8", appConfigData.isJava8Enabled());
        shared.put("servicePackageName", serviceConfigData.getPackageName());
        shared.put("serviceImplPackageName", serviceConfigData.getImplPackageName());
        shared.put("serviceTestPackageName", serviceConfigData.getTestPackageName());
        shared.put("modelPackageName", modelConfigData.getPackageName());
        templateManager.setSharedVariables(shared);
    }

    public String getClassName() {
        if (StringUtils.isBlank(className)) {
            JdbcConfigData jdbcConfigData = ConfigManager.getConfig(JdbcConfigData.class);
            className = NameUtils.tableNameToClassName(tableName, jdbcConfigData.getPrefixList(), jdbcConfigData.isIncludePrefix());
        }
        return className;
    }

    public String getServiceName() {
        if (StringUtils.isBlank(serviceName)) {
            serviceName = getClassName() + "Service";
        }
        return serviceName;
    }

    public String getServiceImplName() {
        if (StringUtils.isBlank(serviceImplName)) {
            serviceImplName = getServiceName() + "Impl";
        }
        return serviceImplName;
    }

    public String getServiceTestName() {
        if (StringUtils.isBlank(serviceTestName)) {
            serviceTestName = getServiceName() + "Test";
        }
        return serviceTestName;
    }

    public void setTableName(String tableName) {
        this.tableName = tableName;
    }

    public void saveToFile() {
        AppConfigData appConfigData = ConfigManager.getConfig(AppConfigData.class);
        ServiceConfigData serviceConfigData = ConfigManager.getConfig(ServiceConfigData.class);

        Template template = TemplateManager.getInstance().getTemplate("service.tpl");
        template.binding("modelName", getClassName());
        template.binding("tableName", tableName);
        template.binding("serviceName", getServiceName());
        Writer interfaceWriter = FileWriterUtils.createWriter(appConfigData.getOutputDirPath(), serviceConfigData.getPackageName(), getServiceName());
        template.renderTo(interfaceWriter);

        template = TemplateManager.getInstance().getTemplate("service-impl.tpl");
        template.binding("modelName", getClassName());
        template.binding("tableName", tableName);
        template.binding("serviceName", getServiceName());
        template.binding("serviceImplName", getServiceImplName());
        Writer implWriter = FileWriterUtils.createWriter(appConfigData.getOutputDirPath(), serviceConfigData.getImplPackageName(), getServiceImplName());
        template.renderTo(implWriter);

        template = TemplateManager.getInstance().getTemplate("service-test.tpl");
        template.binding("modelName", getClassName());
        template.binding("tableName", tableName);
        template.binding("serviceName", getServiceName());
        template.binding("serviceInstName", StringUtils.uncapitalize(getServiceName()));
        Writer testWriter = FileWriterUtils.createWriter(appConfigData.getOutputDirPath(), serviceConfigData.getTestPackageName(), getServiceTestName());
        template.renderTo(testWriter);
    }

}
